#ifndef _ISCHEDULER_H_
#define _ISCHEDULER_H_

#include "TiposDB.h"

/**
 * \brief Interfaz publica del modulo ``Administrador de tareas local (Scheduler)''.
 *
 * Esta version no implementa funcionalidad de ningun tipo, simplemente
 * devuelve valores fijos segun los parametros recibidos.
 *
 * \version 0.2
 */
class IScheduler {

public:
	virtual ~IScheduler(){}

	/**
	 * \brief Crea una nueva base de datos.
	 * \param nombreDB Nombre de la nueva base de datos
	 * \return \li RESULT_OK si nombreDB != "DB1"
	 *         \li DB_ALREADY_EXISTS si nombreDB == "DB1"
	 */
	virtual int createDB(StringDB nombreDB)=0;

	/**
	 * \brief Borra una base de datos.
	 * \param nombreDB Nombre de la base de datos a eliminar.
	 * \return \li RESULT_OK si nombreDB == "DB1"
	 *         \li DB_IS_BEING_USED si nombreDB == "DB2"
	 *         \li DB_NOT_EXISTS en otro caso
	 */
	virtual int deleteDB(StringDB nombreDB)=0;

	/**
	 * \brief Crea una nueva clase en la base de datos.
	 * \param odl Descripcin en lenguaje ODL de la clase.
	 * \return \li DB_NOT_EXISTS si class.database != "DB1"
	 *         \li CLASS_ALREADY_EXISTS si class.name == "Class1"
	 *         \li RESULT_OK en otro caso
	 */
	virtual int createClass(StringDB odl)=0;

	/**
	 * \brief Borra una clase de la base de datos.
	 * \param nombreClase Nombre de la clase a borrar.
	 * \param nombreDB Nombre de la base de datos en la cual reside la clase a borrar.
	 * \return \li DB_NOT_EXISTS si nombreDB != "DB1"
	 *         \li CLASS_NOT_EXISTS si nombreClase != "Class1"
	 *         \li RESULT_OK en otro caso
	 */
	virtual int deleteClass(StringDB nombreClase, StringDB nombreDB)=0;

	/**
	 * \brief Obtiene una clase de la base de datos.
	 *
	 * En caso satisfactorio, la implementacion dummy devuelve un esquema hardcodeado
	 * en la variable odl.
	 *
	 * \param id Identificador de la clase
	 * \param odl Referencia donde se guardara la descripcion en lenguaje ODL de la clase
	 * \return \li DB_NOT_EXISTS si id.database != "DB1"
	 *         \li CLASS_NOT_EXISTS si id.name != "Class1"
	 *         \li RESULT_OK en otro caso
	 */
	virtual int getClass(ClassId id, StringDB &odl)=0;

	/**
	 * \brief Crea un nuevo objeto en la base de datos.
	 *
	 * En caso satisfactorio, la implementacion dummy devuelve el objectId 1.
	 *
	 * \param odl Especificacion en lenguaje ODL del objeto a crear.
	 * \return \li DB_NOT_EXISTS si database != "DB1"
	 *         \li CLASS_NOT_EXISTS si class != "Class1"
	 *         \li RESULT_OK en otro caso
	 */
	 virtual int createObject(StringDB odl, ObjectId &objectId)=0;

	/**
	 * \brief Borra un objeto de la base de datos.
	 * \param id Identificador del objeto a eliminar.
	 * \return \li DB_NOT_EXISTS si id.classId.database != "DB1"
	 *         \li CLASS_NOT_EXISTS si id.classId.name != "Class1"
	 *         \li OBJECT_NOT_EXISTS si id.instanceId != 1
	 *         \li RESULT_OK en otro caso
	 */
	virtual int deleteObject(ObjectId id)=0;

	/**
	 * \brief Actualiza el estado de un objeto en la base de datos.
	 * \param odl Especificacin ODL completa del nuevo estado del objeto.
	 * \return \li DB_NOT_EXISTS si database != "DB1"
	 *         \li CLASS_NOT_EXISTS si class != "Class1"
	 *         \li OBJECT_NOT_EXISTS si id != 1
	 *         \li RESULT_OK en otro caso
	 */
	virtual int updateObject(StringDB odl)=0;

	/**
	 * \brief Obtiene un objeto de la base de datos.
	 *
	 * En caso satisfactorio, la implementacion dummy devuelve en la variable
	 * odl siempre el mismo objeto hardcodeado (database="DB1", class="Class1", id=1)
	 *
	 * \param id Id del objeto
	 * \param odl Referencia donde se guardara la descripcion ODL del objeto
	 * \return \li DB_NOT_EXISTS si id.classId.database != "DB1"
	 *         \li CLASS_NOT_EXISTS si id.classId.name != "Class1"
	 *         \li OBJECT_NOT_EXISTS si id.instanceId != 1
	 *         \li RESULT_OK en otro caso
	 */
	virtual int getObject(ObjectId id, StringDB &odl)=0;

	/**
	 * \brief Da comienzo a una transaccion.
	 *
	 * En caso satisfactorio, la implementacion dummy devuelve el valor 1 en txnId.
	 *
	 * \param connId Identificador de la conexion
	 * \param clientId Identificador del cliente
	 * \param txnId Referencia donde se guardara el id de la nueva transaccion
	 * \return \li CONN_NOT_EXISTS si connId != 1
	 *         \li CLIENT_NOT_EXISTS si clientId != 1
	 *         \li RESULT_OK en otro caso
	 */
	virtual int beginTransaction(ConnId connId, ClientId clientId, TxnId &txnId)=0;

	/**
	 * \brief Finaliza una transaccion.
	 * \param txnId Identificador de la transaccion
	 * \return \li TXN_NOT_EXISTS si txnId != 1
	 *         \li RESULT_OK en otro caso
	 */
	virtual int endTransaction(TxnId txnId)=0;

	/**
	 * \brief Deshace las operaciones de una transaccion.
	 * \param txnId Identificador de la transaccion
	 * \return \li TXN_NOT_EXISTS si txnId != 1
	 *         \li RESULT_OK en otro caso
	 */
	virtual int rollbackTransaction(TxnId txnId)=0;

	/**
	 * \brief Crea un indice para un conjunto de atributos de un objeto.
	 *
	 * En caso satisfactorio, la implementacion dummy siempre devuelve el
	 * indexId 1.
	 *
	 * \param classId Identificador de la clase a indexar
	 * \param attNames Lista con los nombres de los atributos a indexar
	 * \param type Tipo de indice a crear (identificacin o clasificacion)
	 * \param indexId Referencia donde se guardara el id del nuevo indice.
	 * \return \li DB_NOT_EXISTS si classId.database != "DB1"
	 *         \li CLASS_NOT_EXISTS si classId.name != "Class1"
	 *         \li RESULT_OK en otro caso
	 */
	virtual int createIndex(ClassId classId, StringDBList attNames, IndexType type, IndexId &indexId)=0;

	/**
	 * \brief Elimina un indice.
	 * \param id Identificador del indice a eliminar
	 * \return \li INDEX_NOT_EXISTS si id != 1
	 *         \li RESULT_OK si id == 1
	 */
	virtual int deleteIndex(IndexId id)=0;

	/**
	 * \brief Obtiene todos los indices existentes para la clase especificada.
	 *
	 * En caso satisfactorio, la implementacion dummy devuelve la
	 * lista [1, 2] si classId.name == "Class1", o una lista vacia si
	 * classId.name == "Class2".
	 *
	 * \param classId Identificador de la clase.
	 * \param indexIdList Lista donde se guardaran los id de los indices encontrados.
	 * \return \li DB_NOT_EXISTS si classId.database != "DB1"
	 *         \li CLASS_NOT_EXISTS si classId.name != "Class1" y classId.name != "Class2"
	 *         \li RESULT_OK en otro caso
	 */
	virtual int getIndexes(ClassId classId, IndexIdList &indexIdList)=0;

	/**
	 * \brief Obtiene todos los indices que contienen un determinado atributo.
	 *
	 * En caso satisfactorio, la implementacion dummy devuelve la lista
	 * [1, 2] si attName == "Attribute1" y una lista vacia si attName == "Attribute2".
	 *
	 * \param classId Identificador de la clase a la que pertenece el atributo.
	 * \param attName Nombre del atributo.
	 * \param indexIdList Lista donde se guardaran los id de los indices encontrados.
	 * \return \li DB_NOT_EXISTS si classId.database != "DB1"
	 *         \li CLASS_NOT_EXISTS si classId.name != "Class1"
	 *         \li ATTRIBUTE_NOT_EXISTS si attName != "Attribute1" y attName != "Attribute2"
	 *         \li RESULT_OK en otro caso
	 */
	virtual int getIndexesByAttribute(ClassId classId, StringDB attName, IndexIdList &indexIdList)=0;

	/**
	 * \brief Crea un iterador con los objetos indicados.
	 *
	 * En caso satisfactorio, la implementacion dummy siempre devolvera el id 1.
	 *
	 * \param objectIdList Lista con los id de los objetos que contendra el iterador
	 * \param iterId Referencia donde se guardara el id del nuevo iterador
	 * \return \li RESULT_OK en cualquier caso
	 */
	virtual int createIterator(ObjectIdList objectIdList, IteratorId &iterId)=0;

	/**
	 * \brief Crea un iterador con todos los objetos de una clase.
	 *
	 * En caso satisfactorio, la implementacion dummy siempre devolvera el id 1.
	 *
	 * \param classId Id de la clase a iterar
	 * \param iterId Referencia donde se guardara el id del nuevo iterador
	 * \return \li DB_NOT_EXISTS si classId.database != "DB1"
	 *         \li CLASS_NOT_EXISTS si classId.name != "Class1"
	 *         \li RESULT_OK en cualquier otro caso
	 */
	virtual int createIterator(ClassId classId, IteratorId &iterId)=0;

	/**
	 * \brief Crea un iterador con todos los objetos de un indice, filtrados por el valor de uno o varios atributos
	 *
	 * En caso satisfactorio, la implementacion dummy devolvera siempre el id 1.
	 *
	 * \param classId Id de la clase cuyo indice se quiere iterar
	 * \param indexId Id del indice a iterar
	 * \param keyValueList Lista de tuplas (atributo, valor) utilizadas para filtrar
	 * \param iterId Referencia donde se guardara el id del nuevo iterador
	 * \return \li DB_NOT_EXISTS si classId.database != "DB1"
	 *         \li CLASS_NOT_EXISTS si classId.name != "Class1"
	 *         \li INDEX_NOT_EXISTS si indexId != 1
	 *         \li RESULT_OK en cualquier otro caso
	 */
	virtual int createIterator(ClassId classId, IndexId indexId, KeyValueList keyValueList, IteratorId &iterId)=0;

	/**
	 * \brief Elimina un iterador.
	 * \param iteratorId Id del iterador a eliminar.
	 * \return \li ITER_NOT_EXISTS si iteratorId != 1
	 *         \li RESULT_OK si iteratorId == 1
	 */
	virtual int deleteIterator(IteratorId iteratorId)=0;

	/**
	 * \brief Agrega un conjunto de objetos a un iterador.
	 * \param iteratorId Id del iterador al cual agregar los objetos.
	 * \param objectIdLista Lista con los id de los objetos que se quieren agregar al iterador.
	 * \return \li ITER_NOT_EXISTS si iteratorId != 1.
	 *         \li RESULT_OK si iteratorId == 1.
	 */
	virtual int addIdsToIterator(IteratorId iteratorId, ObjectIdList &objectIdList)=0;

	/**
	 * \brief Obtiene el siguiente elemento del iterador.
	 *
	 * En caso satisfactorio, la implementacion dummy devuelve en la variable
	 * odl siempre el mismo objeto hardcodeado (database="DB1", class="Class1", id=1)
	 *
	 * \param id Identificador del iterador.
	 * \param odl Referencia donde se guardara la descripcion del objeto obtenido.
	 * \return \li ITER_NOT_EXISTS si id != 1
	 *         \li RESULT_OK si id == 1
	 */
	virtual int getNextFromIterator(IteratorId id, StringDB &odl)=0;

	/**
	 * \brief Obtiene el id del siguiente elemento del iterador.
	 * \param iteratorId Identificador del iterador.
	 * \param objectId Referencia donde se guardara el id del objeto obtenido.
	 * \return \li ITER_NOT_EXISTS si iteratorId != 1
	 *         \li RESULT_OK si iteratorId == 1
	 */
	virtual int getNextIdFromIterator(IteratorId iteratorId, ObjectId &objectId)=0;

	/**
	 * \brief Obtiene los siguientes n elementos de un iterador.
	 * \param id Id del iterador
	 * \param odlList Lista donde se guardaran las descripciones de los objetos obtenidos.
	 * \param n Cantidad de objetos a obtener.
	 * \return \li ITER_NOT_EXISTS si id != 1
	 *         \li ITER_NUMBER_INVALID si n <= 0
	 *         \li RESULT_OK en cualquier otro caso
	 */
	virtual int getNextsFromIterator(IteratorId id, StringDBList &odlList, LongIntDB n)=0;

	/**
	 * \brief Obtiene los ids de los siguientes n elementos de un iterador.
	 *
	 * En caso satisfactorio, la implementacion dummy devuelve una lista
	 * con n objetos de id (database="DB1", class="Class1", id=i) con i=1,2,...,n
	 *
	 * \param iteratorId Id del iterador
	 * \param objectIdList Lista donde se guardaran los ids de los objetos obtenidos.
	 * \param n Cantidad de objetos a obtener.
	 * \return \li ITER_NOT_EXISTS si id != 1
	 *         \li ITER_NUMBER_INVALID si n <= 0
	 *         \li RESULT_OK en cualquier otro caso
	 */
	virtual int getNextIdsFromIterator(IteratorId id, ObjectIdList &objectIdList, LongIntDB n)=0;

	/**
	 * \brief Obtiene todos los objetos que aparecen al menos una vez como
	 *        valor de un atributo de otra clase.
	 *
	 * En caso satisfactorio, la implementaci�n dummy devuelve siempre el id 1.
	 *
	 * \param classId Id de la clase cuyo atributo se va a observar.
	 * \param attName Nombre del atributo a observar.
	 * \param iteratorId Referencia donde se guardara el id del nuevo iterador
	 * \return \li DB_NOT_EXISTS si classId.database != "DB1"
	 *         \li CLASS_NOT_EXISTS si classId.name != "Class1"
	 *         \li ATTRIBUTE_NOT_EXISTS si attName != "Attribute1"
	 *         \li RESULT_OK en cualquier otro caso
	 */
	virtual int getAttributes(ClassId classId, StringDB attName, IteratorId &iteratorId)=0;

	/**
	 * \brief Devuelve la cantidad de elementos asociados a un iterador.
	 *
	 * En caso satisfactorio, la implementacion dummy siempre devuelve el valor 10.
	 *
	 * \param iteratorId Id del iterador
	 * \param size Referencia donde se guardara la cantidad de elementos del iterador.
	 * \return \li ITER_NOT_EXISTS si iteratorId != 1
	 *         \li RESULT_OK si iteratorId == 1
	 */
	virtual int getSize(IteratorId iteratorId, LongIntDB &size)=0;

};

/***************************************************************************/
/****  CONCRETO   **********************************************************/
/***************************************************************************/

class CScheduler: public IScheduler
{

public:

	virtual int createDB(StringDB nombreDB);
	virtual int deleteDB(StringDB nombreDB);
	virtual int createClass(StringDB odl);
	virtual int deleteClass(StringDB nombreClase, StringDB nombreDB);
	virtual int getClass(ClassId id, StringDB &odl);
    virtual int createObject(StringDB odl, ObjectId &objectId);
	virtual int deleteObject(ObjectId id);
	virtual int updateObject(StringDB odl);
	virtual int getObject(ObjectId id, StringDB &odl);
	virtual int beginTransaction(ConnId connId, ClientId clientId, TxnId &txnId);
	virtual int endTransaction(TxnId txnId);
	virtual int rollbackTransaction(TxnId txnId);
	virtual int createIndex(ClassId classId, StringDBList attNames, IndexType type, IndexId &indexId);
	virtual int deleteIndex(IndexId id);
	virtual int getIndexes(ClassId classId, IndexIdList &indexIdList);
	virtual int getIndexesByAttribute(ClassId classId, StringDB attName, IndexIdList &indexIdList);
	virtual int createIterator(ObjectIdList objectIdList, IteratorId &iterId);
	virtual int createIterator(ClassId classId, IteratorId &iterId);
	virtual int createIterator(ClassId classId, IndexId indexId, KeyValueList keyValueList, IteratorId &iterId);
	virtual int deleteIterator(IteratorId iteratorId);
	virtual int addIdsToIterator(IteratorId iteratorId, ObjectIdList &objectIdList);
	virtual int getNextFromIterator(IteratorId id, StringDB &odl);
	virtual int getNextIdFromIterator(IteratorId iteratorId, ObjectId &objectId);
	virtual int getNextsFromIterator(IteratorId id, StringDBList &odlList, LongIntDB n);
	virtual int getNextIdsFromIterator(IteratorId id, ObjectIdList &objectIdList, LongIntDB n);
	virtual int getAttributes(ClassId classId, StringDB attName, IteratorId &iteratorId);
	virtual int getSize(IteratorId iteratorId, LongIntDB &size);

};



#endif


